import { CSSProperties, forwardRef, useContext, useEffect, useImperativeHandle, useMemo, useRef, useState } from "react"
import './WordEdit.scss';
import {
    Editor,
    EditorState,
    RichUtils,
    Modifier,
    convertFromHTML,
    convertFromRaw,
    convertToRaw,
    DraftBlockType,
    CompositeDecorator,
    ContentBlock,
    ContentState,
    CharacterMetadata,
    DraftInlineStyle,
    SelectionState,
    BlockMap,
    DraftHandleValue
} from 'draft-js';
import CustomInlineInputEl from "./CustomInlineInputEl";
import {
    ChangeBackgroundParagraphParams,
    WordParagraphBlock,
    DeviceEntityRange,
    DocInstance,
    TopicType,
    WordParagraphType,
    SpeciesInfoType
} from "../../../utils/types";
import comDocContext from '../../../context/DocContext';
import {
    adaptFontFamily,
    adaptFontSize2Px,
    convertStyleMapToObject,
    deepCopy,
    findLastTreeNode,
    findNodesWithChildren,
    fontFamilyList,
    fontSizeList,
    insertArrayAtPosition,
    isEmpty,
    toastShort,
} from "../../../utils";
import { WordEditStyleType, TypeFontFamily, TypeFontSize, EditorColorPickerType, DraftBlockData } from "../../../types";
import { DraftStyleMap } from "draft-js";
import {
    moveSelectionToEnd,
    checkIsParagraphTitle,
    getInlineStyleRangesForBlock,
    getDeviceParagraphSpecialTextEntities,
    getDeviceEntityTag,
    replaceTextByRange,
    getInitializedRawContent,
    getEditorBlockParagraphTypeByBlockKey,
    getEditorBlockParagraphTypeByContentBlock,
    generateBlockId,
    replaceDocInfo,
    preProcessComDocInstanceBeforeUpdate,
    findSpeciesInText,
    findSpeciesInTextV2,
    getTwoTextDiffLen,
} from "./WordEditorHelper";
import SpecialTextWithInput from "./SpecialTextWithInput";
import SpecialTextContentEditable from "./SpecialTextContentEditable";
import EditorContext from "../../../context/EditorContext";
import useStateDebounce from "../../../hooks/useStateDebounce";
import CustomEntityDecorator from "./CustomEntityDecorator";
import ReadOnlySpecialText from "./ReadOnlySpecialText";
import LaTexBlock from "./LaTexBlock";
import WordEditorTable from "./WordEditorTable";
import { update } from "lodash";
import WordEditorContextMenu from "../word-editor/WordEditorContextMenu";
import { userInfo } from "os";

interface Props {
    getIsForeground: Function
}

type ColorStyleMap = Map<string, { color: string, hex: string }>

const PageBreakComponent = () => <div className="test111" />;

const WordEditorV2 = (props: Props, ref: any) => {
    useImperativeHandle(ref, () => ({
        toggleLayoutVisible,
        handleChangeMainResize,
        getWordExportParams,
        fillSpeciesInfoList: fillSpeciesInfoListV2,
        changeBackgroundParagraph,
        insertSocialResultsTopicList,
        insertEconomicBenefitAnalysisParagraphList,
        insertEcologicalBenefitAnalysisParagraphList,
        insertCustomBackgroundListToTourismCapacityTopic,
        insertCustomBackgroundListToCurrentParagraph,
        insertCustomBackgroundListToWordLastTopic,
        handleSetFocusDocItem
    }))

    const {
        comDocInstance,
        _setComDocInstance,
        _setCurrentFocusedDocItem,
        comFocusTopicNode,
        comDocConfig
    } = useContext(comDocContext);

    const {
        getIsForeground
    } = props;

    const containerRef = useRef<any>(null);
    const wordEditorRef = useRef<any>(null);
    const containerWidthRule = useRef<string>(null);
    const isEditorFocus = useRef<boolean>(false);

    const delayerScrollToTargetBlockTimer = useRef(null);

    const isComposing = useRef(false);

    const tempComDocInstance = useRef<DocInstance>(comDocInstance);
    const tempTopicList = useRef<TopicType[]>(null);
    const [topicList, setTopicList] = useState<TopicType[]>([]);

    const backgroundColorStyleMap: ColorStyleMap = new Map();
    const textColorStyleMap: ColorStyleMap = new Map();

    const [wordEditorStyleMap, setWordEditStyleMap] = useState<DraftStyleMap>({});

    const [editorState, setEditorState] = useState<EditorState>(EditorState.createEmpty());
    const currentEditorStateRef = useRef<EditorState>(null);
    const editorStateChangeTimeoutRef = useRef(null);
    const editorStateRefreshimeoutRef = useRef(null);

    //当前编辑页面使用
    const [delayUpdateComDocInstance, setDelayUpdateComDocInstance] = useState<DocInstance>(comDocInstance);

    const debouncedComDocInstance = useStateDebounce(delayUpdateComDocInstance, 1000 * 1.5);

    const deviceEntityRangeCacheList = useRef<DeviceEntityRange[]>([]);

    const editorStateDelayInitTimeoutRef = useRef(null);

    const editorStateInitialized = useRef<boolean>(false);

    const updateTopicAttributeDelayTimer1 = useRef<any>(null);  //文本段落修改的延迟
    const updateTopicAttributeDelayTimer2 = useRef<any>(null);  //文本段落中topic属性修改的延迟
    const updateTopicAttributeDelayTimer3 = useRef<any>(null);  //文本段落被删除的延迟

    const scrollContentRef = useRef(null);

    const wordEditorFocusTrackLineRef = useRef<any>(null);

    const wordEditorHighLightTrackLineRef = useRef<any>(null);

    const wordEditorContextMenuRef = useRef<any>(null);

    const isWordEditorContextMenuOpened = useRef<boolean>(false);

    const delayHighLightTimer = useRef<any>(null);

    const delaySetCurrentFocusParagraphBlockTimer = useRef<any>(null);

    const currentFocusedDocItemKey = useRef<string>(null);


    useEffect(() => {
        return () => {
            delayHighLightTimer.current && clearTimeout(delayHighLightTimer.current);
            editorStateChangeTimeoutRef.current && clearTimeout(editorStateChangeTimeoutRef.current)
            editorStateRefreshimeoutRef.current && clearTimeout(editorStateRefreshimeoutRef.current)
            editorStateDelayInitTimeoutRef.current && clearTimeout(editorStateDelayInitTimeoutRef.current);
            updateTopicAttributeDelayTimer1.current && clearTimeout(updateTopicAttributeDelayTimer1.current);
            updateTopicAttributeDelayTimer2.current && clearTimeout(updateTopicAttributeDelayTimer2.current);
            updateTopicAttributeDelayTimer3.current && clearTimeout(updateTopicAttributeDelayTimer3.current);
            delaySetCurrentFocusParagraphBlockTimer.current && clearTimeout(delaySetCurrentFocusParagraphBlockTimer.current);
            delayerScrollToTargetBlockTimer.current && clearTimeout(delayerScrollToTargetBlockTimer.current)
        }
    }, []);

    useEffect(() => {
        try {
            if (comFocusTopicNode) {
                let wordParagraphList = comFocusTopicNode.wordParagraphList;
                let wordEditorFocusTrackLineHeight = 0;
                let wordEditorFocusTrackLineOffsetTop = 0;
                if (comFocusTopicNode.topicType == 'text') {
                    if (!isEmpty(wordParagraphList) && wordParagraphList.length) {
                        wordParagraphList.forEach(wordParagrah => {
                            const blockEl = document.querySelector(`div[data-offset-key="${wordParagrah.blockId}-0-0"]`);
                            //@ts-ignore 
                            const blockOffsetTop = blockEl.offsetTop;
                            if (wordEditorFocusTrackLineOffsetTop == 0) {
                                wordEditorFocusTrackLineOffsetTop = blockOffsetTop;
                            }
                            wordEditorFocusTrackLineHeight += blockEl.clientHeight;
                        })
                    }
                } else if (comFocusTopicNode.topicType == 'device') {
                    if (!comFocusTopicNode.checked) {
                        return toastShort('error', '此设施/设备节点未勾选，暂无法在规划报告中完成检索')
                    }
                    const findTextTopic = comDocInstance.topicList.find(node => {
                        return node.id == comFocusTopicNode.pid;
                    })
                    wordParagraphList = findTextTopic.wordParagraphList;
                    if (!isEmpty(wordParagraphList) && wordParagraphList.length) {
                        wordParagraphList.forEach(wordParagrah => {
                            if (wordParagrah.paragraphType == 'device_background_paragraph') {
                                const blockEl = document.querySelector(`div[data-offset-key="${wordParagrah.blockId}-0-0"]`);
                                //@ts-ignore 
                                const blockOffsetTop = blockEl.offsetTop;
                                if (wordEditorFocusTrackLineOffsetTop == 0) {
                                    wordEditorFocusTrackLineOffsetTop = blockOffsetTop;
                                }
                                wordEditorFocusTrackLineHeight += blockEl.clientHeight;
                            }
                        })
                    }
                }
                // console.log("wordEditorFocusTrackLineHeight--->", wordEditorFocusTrackLineHeight, wordEditorFocusTrackLineOffsetTop)
                scrollContentRef.current.scrollTo({
                    top: wordEditorFocusTrackLineOffsetTop,
                    behavior: 'smooth',
                });
                wordEditorFocusTrackLineRef.current.style.height = wordEditorFocusTrackLineHeight + 'px';
                wordEditorFocusTrackLineRef.current.style.top = wordEditorFocusTrackLineOffsetTop + 'px';
            }
        } catch (e) {
            // console.log("查找comFocusTopicNode对应的文档锚点--->失败", e)
            toastShort('warning', '无法自动聚焦文本段落')
        }
    }, [comFocusTopicNode]);

    const toggleLayoutVisible = (visible: boolean) => {
        // if (visible) {
        //     containerRef.current.style.zIndex = 10;
        //     containerRef.current.style.zIndex = 10;
        //     containerRef.current.style.visibility = 'visible';
        //     // containerRef.current.style.display = 'flex';
        //     // containerRef.current.style.width = containerWidthRule.current;
        // } else {
        //     containerRef.current.style.zIndex = -999;
        //     containerRef.current.style.visibility = 'hidden';
        //     // containerRef.current.style.display = 'none';
        //     // containerRef.current.style.width = 0;
        // }
    };

    const getWordExportParams = () => {
        const contentState = editorState.getCurrentContent();
        const rawContentState = convertToRaw(contentState);
        let tempRawContentState = deepCopy(rawContentState);
        delete tempRawContentState.entityMap;
        let filterBlocks = tempRawContentState.blocks.filter(ele => {
            return ele.text && ele.type && ele.key
        })
        filterBlocks.forEach(block => {
            if (block.data && block.data.wordParagraph && block.data.wordParagraph.tableData) {
                let newTableData: string[][] = block.data.wordParagraph.tableData;
                newTableData.forEach(row => {
                    row.forEach(str => {
                        if (isEmpty(str)) {
                            str = ' ';
                        } else {
                            str = str.toString();
                        }
                    })
                })
                block.data.wordParagraph.tableData = JSON.stringify(newTableData);
                block.data.wordParagraph.tableRowSpanList = block.data.wordParagraph.tableRowSpanList;
                block.data.wordParagraph.tableColSpanList = block.data.wordParagraph.tableColSpanList;
            }
            delete block.depth;
            delete block.key;
            delete block.entityRanges;
            // delete block.inlineStyleRanges;
        })
        tempRawContentState.blocks = filterBlocks;
        const exportWordParams = JSON.stringify(tempRawContentState);
        // console.log("exportWordParams---->", exportWordParams);
        return exportWordParams;
    }

    /**
     * 自定义Entity策略函数
     * @param contentBlock 
     * @param callback 
     * @param contentState 
     */
    const specialTextStrategy = (contentBlock, callback, contentState) => {
        contentBlock.findEntityRanges(
            (character) => {
                const entityKey = character.getEntity();
                return (
                    entityKey !== null &&
                    contentState.getEntity(entityKey).getType() === 'SPECIAL_TEXT'
                );
            },
            callback
        );
    };

    const specialTextDecorator = new CompositeDecorator([
        {
            strategy: specialTextStrategy,
            component: SpecialTextWithInput,
            // component: ReadOnlySpecialText,
            // component: CustomEntityDecorator,
        },
    ]);

    const inlineStyleList: WordEditStyleType[] = [
        //预设字体
        {
            styleName: 'HeiTi',
            styleRule: {
                fontFamily: 'SourceHanSansRegular'
            }
        },
        {
            styleName: 'SongTi',
            styleRule: {
                fontFamily: 'SourceHanSerif'
            }
        },
        {
            styleName: 'YaHei',
            styleRule: {
                fontFamily: 'WeiRuanYaHei'
            }
        },
        {
            styleName: 'TimesNewRoman',
            styleRule: {
                fontFamily: 'WeiRuanYaHei'
            }
        },
        //
        {
            styleName: 'BOLD',
            styleRule: {
                fontWeight: 'bold'
            }
        },
        {
            styleName: 'ITALIC',
            styleRule: {
                fontStyle: 'italic'
            }
        },
        {
            styleName: "delete-line",
            styleRule: {
                textDecoration: 'line-through'
            }
        },
        //
        {
            styleName: "inline_background_color-#ffff00",
            styleRule: {
                backgroundColor: '#ffff00'
            }
        },
        {
            styleName: "inline_background_color-#ff000032",
            styleRule: {
                backgroundColor: '#ff000032'
            }
        },
        {
            styleName: "inline_background_color-blue",
            styleRule: {
                backgroundColor: 'blue'
            }
        },
        {
            styleName: "inline_background_color-red",
            styleRule: {
                backgroundColor: 'red'
            }
        },
        {
            styleName: "normal_inline_style",
            styleRule: {
                fontSize: '14pt',
                letterSpacing: 'normal',
                color: '#000000',
                // lineHeight: '2em'
                // color: 'red'
                // textDecorationLine: 'underline',
                // textDecorationColor: 'red',
                // textUnderlineOffset: 3,
                // textDecorationStyle: 'wavy'
            }
        },
        {
            styleName: "wavy_inline_style",
            styleRule: {
                // textDecorationLine: 'underline',
                // textDecorationColor: '#f2f2f2',
                // textDecorationColor: '#fff',
                // textUnderlineOffset: 3,
                // textDecorationStyle: 'wavy'
            }
        }
    ]


    useEffect(() => {
        //初始化...
        //1、加载预设样式
        //2、
        const defaultStyleMap: Map<string, CSSProperties> = new Map();
        defaultStyleMap.set('SUPERSCRIPT', {
            verticalAlign: 'super',
            fontSize: '10px'
        });
        defaultStyleMap.set('SUBSCRIPT', {
            verticalAlign: 'sub',
            fontSize: '10px'
        })
        fontFamilyList.forEach(fontFamily => {
            defaultStyleMap.set(fontFamily, {
                fontFamily: adaptFontFamily(fontFamily)
            })
        });
        fontSizeList.forEach(fontSize => {
            defaultStyleMap.set(fontSize, {
                fontSize: adaptFontSize2Px(fontSize) + 'px',
                lineHeight: adaptFontSize2Px(fontSize) * 1.5 + 'px',
            })
        });
        inlineStyleList.forEach(inlineStyle => {
            defaultStyleMap.set(inlineStyle.styleName, inlineStyle.styleRule)
        })
        setWordEditStyleMap(convertStyleMapToObject(defaultStyleMap))
    }, []);

    const generateStyleMap = (styleColorType: EditorColorPickerType, toggledColor: string) => {
        console.log("generateStyleMap---->", styleColorType, toggledColor)
        // let styleMap = defaultStyleMap;
        let colorStyleMap: ColorStyleMap = new Map();
        switch (styleColorType) {
            case 'INLINE_BACKGROUND_COLOR':
                colorStyleMap = backgroundColorStyleMap;
                break;
            case 'TEXT_COLOR':
                colorStyleMap = textColorStyleMap;
                break;
            default:
                break;
        };
        // Array.from(colorStyleMap).forEach(colorStyleMapEle => {
        //     const currenStyleMapEleKey = colorStyleMapEle[0];
        //     const currenStyleMapEleType = colorStyleMapEle[0].split('-')[0];
        //     if (!styleMap.has(currenStyleMapEleKey)) {
        //         switch (styleColorType) {
        //             case 'INLINE_BACKGROUND_COLOR':
        //                 styleMap.set(toggledColor, {
        //                     backgroundColor: backgroundColorStyleMap.get(toggledColor)?.color
        //                 })
        //                 break;
        //             case 'TEXT_COLOR':
        //                 styleMap.set(toggledColor, {
        //                     color: textColorStyleMap.get(toggledColor)?.color
        //                 })
        //                 break;
        //             default:
        //                 break;
        //         }
        //     }
        // });
        // return styleMap;
    };

    useEffect(() => {
        console.log("===================编辑器延迟上报数据触发==============")
        _setComDocInstance(deepCopy(tempComDocInstance.current))
    }, [debouncedComDocInstance])


    /********* public方法 *********/
    /**
     * 更换背景文本
     * @param params 
     */
    const changeBackgroundParagraph = (params: ChangeBackgroundParagraphParams) => {
        const {
            topicWordParagraphList,
            currentInUseBackgroundParagraphIndex,
            focusParagraphBlock,
            textTopicId
        } = params;
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        for (let i = 0; i < _tempTopicList.length; i++) {
            if (_tempTopicList[i].id == textTopicId) {
                _tempTopicList[i].currentInUseBackgroundParagraphIndex = currentInUseBackgroundParagraphIndex;
                let oldWordParagraphList: WordParagraphBlock[] = _tempTopicList[i].wordParagraphList;
                let findStartParagraphIndex = -1;
                for (let p = 0; p < oldWordParagraphList.length; p++) {
                    if (oldWordParagraphList[p].paragraphType == 'default_background_paragraph') {
                        findStartParagraphIndex = p;
                        break;
                    }
                }
                if (findStartParagraphIndex > -1) {
                    let filterParagraphList = oldWordParagraphList.filter(item => {
                        return item.paragraphType !== 'default_background_paragraph';
                    })
                    filterParagraphList = insertArrayAtPosition(filterParagraphList, topicWordParagraphList, findStartParagraphIndex);
                    _tempTopicList[i].wordParagraphList = filterParagraphList;
                }
                break;
            }
        }
        _tempComDocInstance.topicList = deepCopy(_tempTopicList);
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState(textTopicId);
    }

    //大熊猫，测试南方红豆杉,测试金钱豹201只， 川金丝猴100只，黔金丝猴1200只，滇金丝猴20只，白尾海雕，白尾海雕，测试雪豹29只, 川金丝猴
    const fillSpeciesInfoList = (speciesInfoList: SpeciesInfoType[]) => {
        console.log("word编辑器内部fillSpeciesInfoList---->", speciesInfoList)
        const contentState = editorState.getCurrentContent();
        const selectionState = editorState.getSelection();
        const anchorKey = selectionState.getAnchorKey();
        const _anchorKey = currentFocusedDocItemKey.current;
        const currentBlock = contentState.getBlockForKey(_anchorKey);
        const blockLength = currentBlock.getLength();
        const cursorPosition = selectionState.getStartOffset();
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        const currentBlockText = currentBlock.getText();
        console.log("currentBlockText", currentBlockText);
        const wordParagrah: WordParagraphBlock = currentBlock.getData().get('wordParagraph')
        const findTextTopic = _tempTopicList.find(topic => {
            return topic.id == wordParagrah.textTopicId;
        })
        const wordParagraphList = findTextTopic.wordParagraphList;
        let findIndex = -1;
        for (let i = 0; i < wordParagraphList.length; i++) {
            if (wordParagraphList[i].blockId === anchorKey) {
                findIndex = i;
                break;
            }
        }
        if (findIndex > -1) {
            let currentWordParagraph = wordParagraphList[findIndex];
            console.log("currentWordParagraph---->", currentWordParagraph)
            let exsitSpeciesName = false;
            speciesInfoList.forEach(speciesInfo => {
                if (currentBlockText && currentBlockText.includes(speciesInfo.species_c)) {
                    exsitSpeciesName = true;
                }
            })
            if (!exsitSpeciesName) {
                return toastShort('warning', '当前段落不包含物种清单的物种名称')
            }
            const {
                replacedText,
                inlineStyleRanges
            } = findSpeciesInTextV2(currentBlockText, speciesInfoList);
            console.log("newBlockText--->", replacedText, inlineStyleRanges)
            if (replacedText == currentWordParagraph.text) {
                return toastShort('warning', '当前段落已完成拉丁名填充')
            } else {
                currentWordParagraph.text = replacedText;
                //@ts-ignore
                currentWordParagraph.inlineStyleRanges = inlineStyleRanges;
            }
        } else {
            return toastShort('error', '操作失败')
        }
        findTextTopic.wordParagraphList = [...wordParagraphList];
        _tempComDocInstance = { ..._tempComDocInstance };
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState(_anchorKey);
    }

    const fillSpeciesInfoListV2 = (speciesInfoList: SpeciesInfoType[]) => {
        console.log("fillSpeciesInfoListV2---->", speciesInfoList)
        const contentState = editorState.getCurrentContent();
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        let _speciesInfoList = speciesInfoList;
        _tempTopicList.forEach(topic => {
            if (topic.topicType == 'text') {
                const wordParagraphList = topic.wordParagraphList;
                wordParagraphList.forEach((wordParagraphBlock, index) => {
                    if (isEmpty(wordParagraphBlock.entityRanges) || wordParagraphBlock.entityRanges.length == 0) {
                        console.log("纯文本的段落")
                    } else {
                    }
                    const currentBlockText = wordParagraphBlock.text;
                    const {
                        replacedText,
                        inlineStyleRanges,
                        newSpeciesList
                    } = findSpeciesInTextV2(currentBlockText, _speciesInfoList);
                    _speciesInfoList = [...newSpeciesList];
                    console.log("replacedText--->", replacedText)
                    console.log("newSpeciesList--->", newSpeciesList)
                    if (replacedText == wordParagraphBlock.text) {
                        // return toastShort('warning', '当前段落已完成拉丁名填充')
                    } else {
                        wordParagraphBlock.text = replacedText;
                        //@ts-ignore
                        wordParagraphBlock.inlineStyleRanges = inlineStyleRanges;
                    }
                })
            }
        })
        _tempComDocInstance = { ..._tempComDocInstance };
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState();
    }

    /**
     * 插入经济效益评价
     * @param wordParagraphList 
     */
    const insertEconomicBenefitAnalysisParagraphList = (wordParagraphList: WordParagraphBlock[]) => {
        console.log("insertEconomicBenefitAnalysisParagraphList--->", wordParagraphList);
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        let targetWordParagraphBlockId = '';
        for (let i = 0; i < _tempTopicList.length; i++) {
            if (_tempTopicList[i].topicTag == 'EconomicBenefitAnalysis') {
                const currentTopic = _tempTopicList[i];
                const oldWordParagraphList = currentTopic.wordParagraphList;
                // targetWordParagraphBlockId = _tempTopicList[i].id;
                wordParagraphList.forEach(wordParagraph => {
                    const currentBlockId = generateBlockId();
                    if (!targetWordParagraphBlockId) {
                        targetWordParagraphBlockId = generateBlockId();
                    }
                    wordParagraph.textTopicId = currentTopic.id;
                    wordParagraph.paragraphType = wordParagraph.paragraphType ? wordParagraph.paragraphType : 'custom_background_paragraph'
                    wordParagraph.text = wordParagraph.text;
                    wordParagraph.blockId = currentBlockId;
                    wordParagraph.paragraphStyle = wordParagraph.paragraphStyle ? wordParagraph.paragraphStyle : 'normal_paragraph';
                    //@ts-ignore
                    wordParagraph.inlineStyleRanges = [{ style: 'normal_inline_style', offset: 0, length: wordParagraph.text.length }];
                })
                currentTopic.wordParagraphList = [oldWordParagraphList[0]].concat(wordParagraphList);
                break;
            }
        }
        _tempComDocInstance.topicList = deepCopy(_tempTopicList);
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState(targetWordParagraphBlockId);
        delayScrollToTargetBlock(targetWordParagraphBlockId);
    }

    /**
     * 插入生态效益评价
     * @param wordParagraphList 
     */
    const insertEcologicalBenefitAnalysisParagraphList = (wordParagraphList: WordParagraphBlock[]) => {
        // console.log("wordParagraphList--->", wordParagraphList)
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        let targetWordParagraphBlockId = '';
        for (let i = 0; i < _tempTopicList.length; i++) {
            if (_tempTopicList[i].topicTag == 'EcologicalBenefitAnalysis') {
                const currentTopic = _tempTopicList[i];
                // targetWordParagraphBlockId = _tempTopicList[i].id;
                const oldWordParagraphList = currentTopic.wordParagraphList;
                wordParagraphList.forEach(wordParagraph => {
                    const currentBlockId = generateBlockId();
                    if (!targetWordParagraphBlockId) {
                        targetWordParagraphBlockId = currentBlockId;
                    }
                    wordParagraph.textTopicId = currentTopic.id;
                    wordParagraph.text = wordParagraph.text;
                    wordParagraph.blockId = currentBlockId;
                    wordParagraph.paragraphStyle = wordParagraph.paragraphStyle ? wordParagraph.paragraphStyle : 'normal_paragraph';
                    wordParagraph.paragraphType = wordParagraph.paragraphType ? wordParagraph.paragraphType : 'custom_background_paragraph'
                    //@ts-ignore
                    wordParagraph.inlineStyleRanges = [{ style: 'normal_inline_style', offset: 0, length: wordParagraph.text.length }];
                })
                currentTopic.wordParagraphList = [oldWordParagraphList[0]].concat(wordParagraphList);
                break;
            }
        }
        _tempComDocInstance.topicList = deepCopy(_tempTopicList);
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState(targetWordParagraphBlockId);
        delayScrollToTargetBlock(targetWordParagraphBlockId);
    }

    /**
     * 社会效益分析
     * @param checkedTopicList 
     */
    const insertSocialResultsTopicList = (checkedTopicList: TopicType[]) => {
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        let findIndex = -1;
        let _checkedTopicList: TopicType[] = [];
        let targetWordParagraphBlockId = '';
        for (let i = 0; i < _tempTopicList.length; i++) {
            if (_tempTopicList[i].topicTag == 'SocialBenefitAnalysis') {
                findIndex = i;
                // targetWordParagraphBlockId = _tempTopicList[i].id;
                _checkedTopicList = checkedTopicList.map(topic => {
                    topic.pid = _tempTopicList[i].id;
                    topic.topicTag = 'SubSocialBenefitAnalysis'
                    //@ts-ignore
                    topic.topicLevel = (Number(_tempTopicList[i].topicLevel) + 1).toString();
                    topic.wordParagraphList.forEach(wordParagraph => {
                        wordParagraph.text = replaceDocInfo(wordParagraph.text, comDocInstance)
                        const currentBlockId = generateBlockId();
                        if (!targetWordParagraphBlockId) {
                            targetWordParagraphBlockId = currentBlockId;
                        }
                        wordParagraph.blockId = currentBlockId;
                        wordParagraph.paragraphStyle = 'normal_paragraph';
                        wordParagraph.paragraphType = 'custom_background_paragraph'
                        //@ts-ignore
                        wordParagraph.inlineStyleRanges = [{ style: 'normal_inline_style', offset: 0, length: wordParagraph.text.length }];
                    })
                    topic.wordParagraphList.unshift({
                        type: 'text',
                        textTopicId: topic.id,
                        paragraphStyle: 'title_paragraph_3',
                        paragraphType: 'topic_title',
                        text: topic.topicName,
                        //@ts-ignore
                        inlineStyleRanges: [{ style: 'normal_inline_style', offset: 0, length: topic.topicName.length }]
                    })
                    // console.log("测试topic.topicLevel", topic.topicLevel)
                    return topic;
                })
            }
            if (_tempTopicList[i].topicTag == 'SubSocialBenefitAnalysis') {
                _tempTopicList.splice(i, 1);
                i--;
            }
        }
        console.log("_tempTopicList---->", _tempTopicList)
        _tempTopicList = _tempTopicList.concat(_checkedTopicList);
        _tempComDocInstance.topicList = deepCopy(_tempTopicList);
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState();
        delayScrollToTargetBlock(targetWordParagraphBlockId);
    }

    /**
     * 环境容量分析, 每次调用，重新在这个大纲节点下生成文本
     * @param tourismCapacityBackgroundList 
     */
    const insertCustomBackgroundListToTourismCapacityTopic = (tourismCapacityBackgroundList: WordParagraphBlock[]) => {
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        let targetWordParagraphBlockId = '';
        for (let i = 0; i < _tempTopicList.length; i++) {
            if (_tempTopicList[i].topicTag == 'EnvironmentalCapacityAnalysis') {
                // targetWordParagraphBlockId = _tempTopicList[i].id;
                let _tourismCapacityBackgroundList: WordParagraphBlock[] = deepCopy(tourismCapacityBackgroundList);
                console.log("_tourismCapacityBackgroundList--->", _tourismCapacityBackgroundList)
                let currentTopicWordParagraphList = _tempTopicList[i].wordParagraphList;
                _tourismCapacityBackgroundList.forEach(wordParagraph => {
                    const currentBlockId = generateBlockId();
                    if (!targetWordParagraphBlockId) {
                        targetWordParagraphBlockId = currentBlockId;
                    }
                    wordParagraph.textTopicId = _tempTopicList[i].id;
                    wordParagraph.blockId = currentBlockId;
                    wordParagraph.paragraphType = 'custom_background_paragraph';
                    wordParagraph.paragraphStyle = 'normal_paragraph';
                    if (wordParagraph.type == 'text') {
                        //@ts-ignore
                        wordParagraph.inlineStyleRanges = [{ style: 'normal_inline_style', offset: 0, length: wordParagraph.text.length }];
                    } else if (wordParagraph.type == 'LaTex') {
                        wordParagraph.text = wordParagraph.expressionLaTex;
                        //@ts-ignore
                        wordParagraph.inlineStyleRanges = [{ style: 'normal_inline_style', offset: 0, length: wordParagraph.expressionLaTex.length }];
                    }
                })
                _tempTopicList[i].wordParagraphList = [currentTopicWordParagraphList[0]].concat(_tourismCapacityBackgroundList);
                console.log("_tempTopicList[i]--->", _tempTopicList[i])
                break;
            }
        }
        _tempComDocInstance.topicList = deepCopy(_tempTopicList);
        tempComDocInstance.current = _tempComDocInstance;
        handleUpdateComDocInstance(_tempComDocInstance);
        refreshWordEditorState(targetWordParagraphBlockId);
    }


    /**
     * 插入段落到光标所处段落，注意：
     * @param customBackgroundList 
     */
    const insertCustomBackgroundListToCurrentParagraph = (customBackgroundList: WordParagraphBlock[]) => {
        try {
            if (isEmpty(currentFocusedDocItemKey.current)) {
                return toastShort("error", '文档编辑器没有聚焦的段落！无法执行插入操作')
            }
            delayScrollToTargetBlock(currentFocusedDocItemKey.current);
            customBackgroundList = [...customBackgroundList];
            const contentState: ContentState = editorState.getCurrentContent();
            const currentBlock: ContentBlock = contentState.getBlockForKey(currentFocusedDocItemKey.current);
            const wordParagrah: WordParagraphBlock = currentBlock.getData().get('wordParagraph');
            const currentBlockText = currentBlock.getText();
            let insertActionType: 'append' | 'replace' = 'replace';
            if (!isEmpty(currentBlockText) && currentBlockText && currentBlockText.length > 0) {
                insertActionType = 'append';
                toastShort('warning', '当前段落已存在文本内容，已为您在该段落下方执行插入操作')
            }
            console.log("wordParagrah----->", wordParagrah)
            let _tempComDocInstance = tempComDocInstance.current;
            let _tempTopicList = _tempComDocInstance.topicList;
            let findIndex = -1;
            customBackgroundList.forEach(paragraph => {
                paragraph.textTopicId = wordParagrah.textTopicId;
                paragraph.blockId = generateBlockId();
                if (paragraph.type == 'Table') {
                    paragraph.text = "表格"
                }
                paragraph.paragraphStyle = paragraph.paragraphStyle ? paragraph.paragraphStyle : 'normal_paragraph';
                paragraph.paragraphType = paragraph.paragraphType ? paragraph.paragraphType : 'custom_background_paragraph'
                //@ts-ignore
                paragraph.inlineStyleRanges = paragraph.inlineStyleRanges ? paragraph.inlineStyleRanges : [{ style: 'normal_inline_style', offset: 0, length: paragraph.text.length }];
            })
            console.log("customBackgroundList---->", customBackgroundList)
            let topicWordParagraphList: WordParagraphBlock[] = [];
            for (let i = 0; i < _tempTopicList.length; i++) {
                if (_tempTopicList[i].id == wordParagrah.textTopicId) {
                    findIndex = i;
                    topicWordParagraphList = _tempTopicList[i].wordParagraphList;
                    break;
                }
            }
            for (let p = 0; p < topicWordParagraphList.length; p++) {
                if (topicWordParagraphList[p].blockId == currentFocusedDocItemKey.current) {
                    if (insertActionType == 'replace') {
                        //删除掉空白段落
                        topicWordParagraphList.splice(p, 1);
                    }
                    topicWordParagraphList = insertArrayAtPosition(topicWordParagraphList, customBackgroundList, insertActionType == 'append' ? p + 1 : p)
                    break;
                }
            }
            _tempTopicList[findIndex].wordParagraphList = deepCopy(topicWordParagraphList);
            _tempComDocInstance.topicList = [..._tempTopicList];
            tempComDocInstance.current = _tempComDocInstance;
            handleUpdateComDocInstance(_tempComDocInstance);
            refreshWordEditorState(currentFocusedDocItemKey.current);
            toastShort('success', '插入成功！')
        } catch (e) {
            console.log("插入失败---->", e)
            toastShort('error', '插入失败')
        }
    }

    /**
     * 
     * @param customBackgroundList 
     */
    const insertCustomBackgroundListToWordLastTopic = (customBackgroundList: WordParagraphBlock[]) => {
        try {
            const contentState = editorState.getCurrentContent();
            // const rawContent = convertToRaw(contentState)
            const blockMap = contentState.getBlockMap();
            console.log("blockMap--->len", blockMap.size)
            // blockMap.forEach((block, key) => {
            //     console.log("block----->", block.getText())
            // })
            // 获取最后一个 block
            const lastContentBlock: ContentBlock = blockMap.last();
            const lastContentBlockKey = lastContentBlock.getKey();
            const wordParagrah: WordParagraphBlock = lastContentBlock.getData().get('wordParagraph');
            console.log("wordParagrah---->", wordParagrah)
            let _tempComDocInstance = tempComDocInstance.current;
            let _tempTopicList = _tempComDocInstance.topicList;
            // console.log("最后一个_tempTopicList---->", _tempTopicList[_tempTopicList.length - 1])
            let findIndex = -1;
            customBackgroundList.forEach(paragraph => {
                paragraph.textTopicId = wordParagrah.textTopicId;
                paragraph.blockId = generateBlockId();
                if (paragraph.type == 'Table') {
                    paragraph.text = "表格"
                }
                paragraph.paragraphStyle = paragraph.paragraphStyle ? paragraph.paragraphStyle : 'normal_paragraph';
                paragraph.paragraphType = paragraph.paragraphType ? paragraph.paragraphType : 'custom_background_paragraph';
                //@ts-ignore
                paragraph.inlineStyleRanges = [{ style: 'normal_inline_style', offset: 0, length: paragraph.text.length }];
            })
            console.log("customBackgroundList---->", customBackgroundList)
            let topicWordParagraphList: WordParagraphBlock[] = [];
            for (let i = 0; i < _tempTopicList.length; i++) {
                if (_tempTopicList[i].id == wordParagrah.textTopicId) {
                    findIndex = i;
                    topicWordParagraphList = _tempTopicList[i].wordParagraphList;
                    break;
                }
            }
            for (let p = 0; p < topicWordParagraphList.length; p++) {
                if (topicWordParagraphList[p].blockId == lastContentBlockKey) {
                    topicWordParagraphList = insertArrayAtPosition(topicWordParagraphList, customBackgroundList, p + 1)
                    break;
                }
            }
            console.log("处理好的topicWordParagraphList---->", topicWordParagraphList)
            _tempTopicList[findIndex].wordParagraphList = deepCopy(topicWordParagraphList);
            _tempComDocInstance.topicList = [..._tempTopicList];
            tempComDocInstance.current = _tempComDocInstance;
            handleUpdateComDocInstance(_tempComDocInstance);
            refreshWordEditorState(lastContentBlockKey ? lastContentBlockKey : null);
            setTimeout(() => {
                // scrollContentRef.current.scrollIntoView({ behavior: 'smooth', block: 'end' });'
                scrollContentRef.current.scrollTop = scrollContentRef.current.scrollHeight;
            }, 100);
            toastShort('success', '插入成功！')
        } catch (e) {
            toastShort('error', '插入失败')
        }
    }

    const handleSetFocusDocItem = (wordParagraph: WordParagraphBlock) => {
        const contentState: ContentState = editorState.getCurrentContent();
        const currentParagraphBlock = contentState.getBlockForKey(wordParagraph.blockId);
        if (currentParagraphBlock) {
            _setCurrentFocusedDocItem(currentParagraphBlock)
            let wordEditorFocusTrackLineHeight = 0;
            let wordEditorFocusTrackLineOffsetTop = 0;
            const blockEl = document.querySelector(`div[data-offset-key="${wordParagraph.blockId}-0-0"]`);
            //@ts-ignore 
            const blockOffsetTop = blockEl.offsetTop;
            if (wordEditorFocusTrackLineOffsetTop == 0) {
                wordEditorFocusTrackLineOffsetTop = blockOffsetTop;
            }
            wordEditorFocusTrackLineHeight += blockEl.clientHeight;
            wordEditorHighLightTrackLineRef.current.style.height = wordEditorFocusTrackLineHeight + 'px';
            wordEditorHighLightTrackLineRef.current.style.top = wordEditorFocusTrackLineOffsetTop + 'px';
            scrollContentRef.current.scrollTo({
                top: wordEditorFocusTrackLineOffsetTop,
                behavior: 'smooth',
            });
            wordEditorFocusTrackLineRef.current.style.height = wordEditorFocusTrackLineHeight + 'px';
            wordEditorFocusTrackLineRef.current.style.top = wordEditorFocusTrackLineOffsetTop + 'px';
        }
    }

    /**
     * 
     * @param oldContentState 
     * @param newContentState 
     * @param blockKey 
     * @returns 
     */
    const updateEntities = (
        oldContentState: ContentState,
        newContentState: ContentState,
        blockKey: string
    ) => {
        const oldBlock = oldContentState.getBlockForKey(blockKey);
        const newBlock: ContentBlock = newContentState.getBlockForKey(blockKey);
        // 创建一个新的 SelectionState 对象
        const selection = SelectionState.createEmpty(blockKey).merge({
            anchorOffset: 0,
            focusOffset: oldBlock.getLength()
        });
        // 将 newBlock 的文本应用到旧的block中
        let updatedContentState = Modifier.replaceText(oldContentState, selection, newBlock.getText());

        // 收集 oldBlock 中的实体范围和实体键
        const oldEntityRanges = [];
        oldBlock.findEntityRanges(
            character => {
                return character.getEntity() !== null;
            },
            (start, end) => {
                const entityKey = oldBlock.getEntityAt(start);
                oldEntityRanges.push({ start, end, entityKey });
            }
        );
        // 收集 newBlock 中的实体范围和实体键
        const newEntityRanges = [];
        newBlock.findEntityRanges(
            characterMetadata => {
                const charEntityKey = characterMetadata.getEntity();
                return charEntityKey !== null;
            },
            (start, end) => {
                const charEntityKey = newBlock.getEntityAt(start);
                const entityData: DeviceEntityRange = newContentState.getEntity(charEntityKey).getData();
                entityData.start = start;
                entityData.end = end;
                entityData.entityKey = charEntityKey;
                let entityRange = {
                    entityKey: charEntityKey,
                    start,
                    end,
                    entityData
                }
                newEntityRanges.push(entityRange);
            }
        );
        console.log("测试newEntityRanges---->", newEntityRanges, oldEntityRanges)

        // 遍历 newEntityRanges，与 oldEntityRanges 中的实体进行对比
        // newEntityRanges.forEach(({ start, end, entityKey }, index) => {
        //     const oldEntityRange = oldEntityRanges[index];

        //     if (oldEntityRange) {
        //         // 合并新实体的数据到旧实体中
        //         const oldEntityKey = oldEntityRange.entityKey;
        //         const oldEntity = updatedContentState.getEntity(oldEntityKey);
        //         const newEntity = newContentState.getEntity(entityKey);

        //         const mergedData = {
        //             ...oldEntity.getData(),
        //             ...newEntity.getData()
        //         };

        //         updatedContentState = updatedContentState.mergeEntityData(oldEntityKey, mergedData);

        //         // 使用新的实体键来更新实体
        //         const selection = SelectionState.createEmpty(blockKey).merge({
        //             anchorOffset: start,
        //             focusOffset: end
        //         });
        //         updatedContentState = Modifier.applyEntity(updatedContentState, selection, oldEntityKey);
        //     }
        // });
        newEntityRanges.forEach(({ start, end, entityKey, entityData }) => {
            // 根据需要更新实体的偏移量，例如：start += 1, end += 1
            const selection = SelectionState.createEmpty(blockKey).merge({
                anchorOffset: start,
                focusOffset: end
            });
            updatedContentState = updatedContentState.replaceEntityData(entityKey, entityData);
            updatedContentState = Modifier.applyEntity(updatedContentState, selection, entityKey);
        });
        return updatedContentState;
    };

    const updateBlockIfNeeded = (oldContentState, newContentState, blockKey) => {
        try {
            const oldBlock = oldContentState.getBlockForKey(blockKey);
            const newBlock = newContentState.getBlockForKey(blockKey);
            if (oldBlock.getText() !== newBlock.getText()) {
                const newText = newBlock.getText();
                const blockLength = oldBlock.getLength();
                const selectionState = oldContentState.getSelectionAfter().merge({
                    anchorKey: blockKey,
                    anchorOffset: 0,
                    focusKey: blockKey,
                    focusOffset: blockLength
                });

                let updatedContentState = Modifier.replaceText(oldContentState, selectionState, newText);
                // 更新实体
                updatedContentState = updateEntities(updatedContentState, newContentState, blockKey);

                const newEditorState = EditorState.push(editorState, updatedContentState, 'change-block-data');
                handleUpdateEditorState(newEditorState)
            }
        } catch (e) {
            console.log("updateBlockIfNeeded-->报错了", e)
        }
    };

    useEffect(() => {
        if (
            isEmpty(comDocInstance) ||
            (comDocInstance.updateComponentName && comDocInstance.updateComponentName == 'WordEditor') ||
            (isEmpty(comDocInstance.topicList) || comDocInstance.topicList.length == 0)
        ) {
            console.log("WordEditor数据不合规拦截")
            return;
        }
        tempComDocInstance.current = comDocInstance;
        tempTopicList.current = tempComDocInstance.current.topicList;
        refreshWordEditorState();
    }, [comDocInstance]);

    const delayScrollToTargetBlock = (targetBlockId: string) => {
        try {
            delayerScrollToTargetBlockTimer.current = setTimeout(() => {
                let wordEditorFocusTrackLineHeight = 0;
                let wordEditorFocusTrackLineOffsetTop = 0;
                const blockEl = document.querySelector(`div[data-offset-key="${targetBlockId}-0-0"]`);
                //@ts-ignore 
                const blockOffsetTop = blockEl.offsetTop;
                if (wordEditorFocusTrackLineOffsetTop == 0) {
                    wordEditorFocusTrackLineOffsetTop = blockOffsetTop;
                }
                wordEditorFocusTrackLineHeight += blockEl.clientHeight;
                scrollContentRef.current.scrollTo({
                    top: wordEditorFocusTrackLineOffsetTop,
                    behavior: 'smooth',
                });
                wordEditorFocusTrackLineRef.current.style.height = wordEditorFocusTrackLineHeight + 'px';
                wordEditorFocusTrackLineRef.current.style.top = wordEditorFocusTrackLineOffsetTop + 'px';
            }, 500);
        } catch (e) {
            console.log("delayScrollToTargetBlock--->err", e)
        }
    }

    const forceUpdateEditorState = (oldEditorState: EditorState, newContentState: ContentState) => {
        const oldContentState = oldEditorState.getCurrentContent();
        const newBlockMap = newContentState.getBlockMap();
        const newEntityMap = newContentState.getEntityMap();
        // 通过将新块映射到相应的块键来替换旧块
        const updatedBlockArray = oldContentState.getBlocksAsArray().map((oldBlock) => {
            const blockKey = oldBlock.getKey();
            return newBlockMap.has(blockKey) ? newBlockMap.get(blockKey) : oldBlock;
        });
        console.log("newEntityMap---->", newEntityMap)
        // 使用更新后的块数组和新实体映射创建一个新的ContentState
        const updatedContentState = ContentState.createFromBlockArray(updatedBlockArray, newEntityMap);
        // 更新EditorState
        const newEditorState = EditorState.push(oldEditorState, updatedContentState, 'change-block-data');
        return newEditorState;
    };

    // const refreshWordEditorStateWithComDocInstance = (newComDocInstance: DocInstance) => {
    //     const {
    //         rawContent,
    //         updatedComDocInstance
    //     } = getInitializedRawContent(tempComDocInstance.current)
    //     console.log("刷新时的rawContent---->", rawContent)
    //     const newContentState = convertFromRaw(rawContent);
    //     const refreshEditorState = EditorState.createWithContent(newContentState, specialTextDecorator);
    //     // const updatedSelection = editorState.getSelection().merge({
    //     //     anchorKey: newContentState.getFirstBlock().getKey(),
    //     //     // anchorOffset: 0,
    //     //     // focusKey: newContentState.getFirstBlock().getKey(),
    //     //     // focusOffset: 0,
    //     //     // hasFocus: true,
    //     // });
    //     const updatedSelection = editorState.getSelection();
    //     const forceUpdatedEditorState = EditorState.forceSelection(refreshEditorState, updatedSelection);
    //     handleUpdateEditorState(forceUpdatedEditorState)
    // }

    const refreshWordEditorState = (focusBlockKey?: string) => {
        console.warn('========编辑器刷新======')
        console.log('focusBlockKey---->', focusBlockKey);
        console.log("编辑器此次使用的最新的tempComDocInstance---->", tempComDocInstance.current)
        const processedComDocInstance = preProcessComDocInstanceBeforeUpdate(tempComDocInstance.current, comDocConfig)
        const {
            rawContent,
            updatedComDocInstance
        } = getInitializedRawContent(processedComDocInstance, comDocConfig)
        console.log("刷新时的rawContent---->", rawContent)
        const newContentState = convertFromRaw(rawContent);
        // console.log("newContentState---->", newContentState)
        const refreshEditorState = EditorState.createWithContent(newContentState, specialTextDecorator);
        // const updatedSelection = editorState.getSelection().merge({
        //     anchorKey: newContentState.getFirstBlock().getKey(),
        //     // anchorOffset: 0,
        //     // focusKey: newContentState.getFirstBlock().getKey(),
        //     // focusOffset: 0,
        //     // hasFocus: true,
        // });
        let updatedSelection = editorState.getSelection();
        if (focusBlockKey) {
            console.log("刷新时设定focusBlockKey--->", focusBlockKey)
            updatedSelection = new SelectionState({
                anchorKey: focusBlockKey,
                anchorOffset: 0,
                focusKey: focusBlockKey,
                focusOffset: 0,
            });
        }
        let forceUpdatedEditorState = EditorState.forceSelection(refreshEditorState, updatedSelection);
        handleUpdateEditorState(forceUpdatedEditorState)
        delayHighLightTimer.current = setTimeout(() => {
            if (focusBlockKey) {
                // delayScrollToTargetBlock(focusBlockKey);
                try {
                    let wordEditorFocusTrackLineHeight = 0;
                    let wordEditorFocusTrackLineOffsetTop = 0;
                    const blockEl = document.querySelector(`div[data-offset-key="${focusBlockKey}-0-0"]`);
                    console.log("blockEl---->", blockEl)
                    if (blockEl) {
                        //@ts-ignore 
                        const blockOffsetTop = blockEl.offsetTop;
                        if (wordEditorFocusTrackLineOffsetTop == 0) {
                            wordEditorFocusTrackLineOffsetTop = blockOffsetTop;
                        }
                        wordEditorFocusTrackLineHeight += blockEl.clientHeight;
                        console.log("wordEditorFocusTrackLineHeight--->", wordEditorFocusTrackLineHeight, wordEditorFocusTrackLineOffsetTop)
                        wordEditorHighLightTrackLineRef.current.style.height = wordEditorFocusTrackLineHeight + 'px';
                        wordEditorHighLightTrackLineRef.current.style.top = wordEditorFocusTrackLineOffsetTop + 'px';
                    }
                } catch (e) {
                    console.log("聚焦失败---->", e)
                }
            }
        }, 500);
    }

    const handleChangeMainResize = (siderBarWidth: number) => {
        containerWidthRule.current = `calc(100% - ${394 + siderBarWidth}px)`;
        containerRef.current.style.width = containerWidthRule.current;
    };

    const adapContainerClassName = () => {
        const contentState = editorState.getCurrentContent();
        let className = 'flex-col word-edit-area-content';
        if (!contentState.hasText()) {
            className += 'flex-col word-edit-area-content-hide-placeholder';
        }
        return className;
    }

    const handleEntityChange = (
        blockKey: string,
        entityKey: string,
        deviceEntityRange: DeviceEntityRange,
        newEntityText: string
    ) => {
        try {
            console.log("Entity的文本内容发生改变", blockKey, entityKey, deviceEntityRange, newEntityText)
            const contentState = editorState.getCurrentContent();
            const selectionState = editorState.getSelection();
            const currentBlockKey = blockKey;
            const currentBlock: ContentBlock = contentState.getBlockForKey(currentBlockKey);
            const entityRanges: DeviceEntityRange[] = [];
            currentBlock.findEntityRanges(
                (characterMetadata) => {
                    const charEntityKey = characterMetadata?.getEntity();
                    return charEntityKey !== null;
                },
                (start, end) => {
                    const charEntityKey = currentBlock.getEntityAt(start);
                    const entityData: DeviceEntityRange = contentState.getEntity(charEntityKey).getData();
                    entityData.start = start;
                    entityData.end = end;
                    entityData.entityKey = charEntityKey;
                    entityRanges.push(entityData);
                }
            );
            console.log("entityRanges--->更新之前", deepCopy(entityRanges));
            let findEntityRangeIndex = -1;
            let totalDiffOffsetLength = 0;
            let optionEntityRangeList: DeviceEntityRange[] = [];
            entityRanges.forEach((entityRange, entityRangeIndex) => {
                if (
                    getDeviceEntityTag(entityRange) == getDeviceEntityTag(deviceEntityRange)
                    // && entityRange.key == deviceEntityRange.key
                ) {
                    entityRange.start = entityRange.start + totalDiffOffsetLength;
                    entityRange.offset = entityRange.start;
                    entityRange.textOffset = entityRange.start;
                    let tempDiffOffsetLength = getTwoTextDiffLen(newEntityText, entityRange.text);
                    // console.log("tempDiffOffsetLength--->", tempDiffOffsetLength)
                    entityRange.diffOffsetLength = tempDiffOffsetLength;
                    entityRange.end = entityRange.start + newEntityText.length;
                    entityRange.text = newEntityText;
                    entityRange.textLength = newEntityText.length;
                    findEntityRangeIndex = entityRangeIndex;
                    optionEntityRangeList.push(entityRange);
                    totalDiffOffsetLength += entityRange.diffOffsetLength;
                } else {
                    entityRange.start = entityRange.start + totalDiffOffsetLength;
                    entityRange.offset = entityRange.start;
                    entityRange.textOffset = entityRange.start;
                    entityRange.textLength = newEntityText.length;
                    entityRange.end = entityRange.end + totalDiffOffsetLength;
                }
            })
            console.log("entityRanges--->更新之后", deepCopy(entityRanges));
            let blockText = currentBlock.getText();
            const blockTextOriginLength = blockText.length;
            console.log("optionEntityRangeList---->", optionEntityRangeList)
            let currentTotalDiffOffsetLength = 0;
            optionEntityRangeList.forEach((optionEntityRange, optionEntityRangeIndex) => {
                if (optionEntityRange.diffOffsetLength) {
                    //第一步：根据optionEntityRange的属性变化，来更新blockText
                    currentTotalDiffOffsetLength += optionEntityRange.diffOffsetLength;
                    const blockTextBeforeSlice = blockText.substring(0, optionEntityRange.start);
                    const blockTextAfterSlice = blockText.slice(optionEntityRange.end - optionEntityRange.diffOffsetLength);
                    console.log("前置切片---->", optionEntityRangeIndex, blockTextBeforeSlice);
                    console.log("后置切片---->", optionEntityRangeIndex, blockTextAfterSlice);
                    blockText = blockTextBeforeSlice + optionEntityRange.text + blockTextAfterSlice;
                }
            })
            console.log("blockText---->最终", blockText);
            //第二步：根据Modifier.replaceText把新的blockText合并到contentState
            let updatedContentState = Modifier.replaceText(
                contentState,
                contentState.getSelectionAfter().merge({
                    anchorKey: currentBlockKey,
                    focusKey: currentBlockKey,
                    anchorOffset: 0,
                    focusOffset: blockTextOriginLength,
                }),
                blockText
            );
            //第三步：根据optionEntityRange的的属性变化，使用Modifier.applyEntity更新contentState对应的entitys
            entityRanges.forEach(({ start, end, entityKey }) => {
                const selection = SelectionState.createEmpty(currentBlockKey).merge({
                    anchorOffset: start,
                    focusOffset: end
                });
                updatedContentState = Modifier.applyEntity(updatedContentState, selection, entityKey);
            });
            const newEditorState: EditorState = EditorState.push(editorState, updatedContentState, 'change-block-data');
            if (entityRanges && entityRanges.length) {
                //最终：把光标移动到entity之后
                const findEntityInstance = updatedContentState.getEntity(entityKey);
                const findEntityInstanceData: DeviceEntityRange = findEntityInstance.getData();
                findEntityInstanceData.text = newEntityText;
                updateTopicByNewEntityData(findEntityInstanceData, entityRanges, newEditorState, blockText);
            }
        } catch (e) {
            console.error(e)
            toastShort('error', "表文联动程序异常，请尽快联系开发人员修复！")
        }
    };

    const updateTopicByNewEntityData = (
        newEnitityData: DeviceEntityRange,
        newEntityRanges: DeviceEntityRange[],
        newEditorState: EditorState,
        blockText: string
    ) => {
        console.log("updateTopicByNewEntityData---->", newEnitityData, newEntityRanges)
        const _tempTopicList = tempTopicList.current;
        const _tempComDocInstance = comDocInstance;
        for (let i = 0; i < _tempTopicList.length; i++) {
            if (_tempTopicList[i].id == newEnitityData.textTopicId) {
                console.log("Entity改变时-找到了需要更新的topic----->", i, _tempTopicList[i], newEntityRanges);
                console.log("测试", _tempTopicList[i].wordParagraphList);
                const deviceWordParagraphBlock = _tempTopicList[i].wordParagraphList.find(wordParagraph => {
                    return wordParagraph.paragraphType == 'device_background_paragraph';
                });
                deviceWordParagraphBlock.text = blockText;
                console.log("deviceWordParagraphBlock---->", deviceWordParagraphBlock)
                let _currentDeviceEntityRanges = deviceWordParagraphBlock.entityRanges;
                _currentDeviceEntityRanges.forEach(deviceEntity => {
                    const findNewDeviceEntity = newEntityRanges.find(entityRange => {
                        return getDeviceEntityTag(entityRange) == getDeviceEntityTag(deviceEntity) &&
                            entityRange.key === deviceEntity.key;
                    })
                    console.log("findNewDeviceEntity---->", findNewDeviceEntity)
                    if (findNewDeviceEntity) {
                        deviceEntity.start = findNewDeviceEntity.start;
                        deviceEntity.text = findNewDeviceEntity.text;
                        deviceEntity.end = findNewDeviceEntity.end;
                        console.log("deviceEntity.end--->", deviceEntity.end)
                    }
                })
                //找到当前文本节点下的设施、设备节点
                const childDeviceTopicList = _tempTopicList.filter(topic => {
                    return topic.pid == _tempTopicList[i].id;
                })
                console.log("更新了topicList的_currentDeviceEntityRanges--->", deepCopy(_currentDeviceEntityRanges));
                console.log("childDeviceTopicList----->", deepCopy(childDeviceTopicList));
                _currentDeviceEntityRanges.forEach(deviceEntity => {
                    const findDeviceTopic = childDeviceTopicList.find(topic => {
                        return topic.id == deviceEntity.deviceTopicId;
                    })
                    if (
                        findDeviceTopic &&
                        findDeviceTopic.id == deviceEntity.deviceTopicId &&
                        newEnitityData.deviceTopicId == deviceEntity.deviceTopicId
                    ) {
                        console.log("deviceEntity.deviceAttributeType--->", deviceEntity.deviceAttributeType, deviceEntity)
                        switch (newEnitityData.deviceAttributeType) {
                            case '$[S]':
                                findDeviceTopic.topicName = newEnitityData.text;
                                break;
                            case '$[X]':
                                // findDeviceTopic.topicName = deviceEntity.text;
                                findDeviceTopic.topicName = newEnitityData.text;
                                break;
                            case '$[N]':
                                // findDeviceTopic.count = deviceEntity.text;
                                findDeviceTopic.count = newEnitityData.text;
                                break;
                            case '$[U]':
                                // findDeviceTopic.unit = deviceEntity.text;
                                findDeviceTopic.unit = newEnitityData.text;
                                break;
                            default:
                                break;
                        }
                        console.log("更新之后findDeviceTopic----->", findDeviceTopic)
                    }
                })
                console.log("更新之后的childDeviceTopicList----->", childDeviceTopicList)
                break;
            }
        }
        console.log("更新之后的_tempTopicList----->", _tempTopicList)
        // 这里直接触发EditorState更新，就会直接同步所有数据，一方面是减少保存次数、另一方面是：也需要更新背景文本(构造好的)
        // 所以也只需要更新文本节点就好了
        _tempComDocInstance.topicList = _tempTopicList;
        tempTopicList.current = _tempTopicList;
        onEditorStateChange(newEditorState);
        tempComDocInstance.current = { ..._tempComDocInstance };
        setDelayUpdateComDocInstance(tempComDocInstance.current)
    }

    const handleUpdateEditorState = (newEditorState: EditorState) => {
        setEditorState(newEditorState);
        currentEditorStateRef.current = newEditorState;
    }

    const handleUpdateComDocInstance = (newComDocInstance: DocInstance) => {
        console.log("文档编辑器派发的新数据--->", newComDocInstance)
        tempComDocInstance.current = newComDocInstance;
        if (editorStateChangeTimeoutRef.current) {
            clearTimeout(editorStateChangeTimeoutRef.current)
        }
        editorStateChangeTimeoutRef.current = setTimeout(() => {
            newComDocInstance.updateComponentName = 'WordEditor';
            // setDelayUpdateComDocInstance(newComDocInstance);
            _setComDocInstance(preProcessComDocInstanceBeforeUpdate(newComDocInstance, comDocConfig))
        }, 300);
    }

    const onEditorStateChange = (newEditorState: EditorState) => {
        console.log("onEditorStateChange----->触发")
        const newContentState = newEditorState.getCurrentContent();
        const oldContentState = editorState.getCurrentContent();
        const newContentBlockMap = newContentState.getBlockMap();
        const oldContentBlockMap = oldContentState.getBlockMap();
        const selectionState = newEditorState.getSelection();
        // console.log("oldContentBlockMap--->", oldContentBlockMap);
        // console.log("newContentBlockMap--->", newContentBlockMap)
        newContentBlockMap.forEach((newBlock, blockKey) => {
            const oldBlock = oldContentBlockMap.get(blockKey);
            if (!oldBlock) {
                console.log(`新增了段落----->${blockKey}`);
                return;
            }
            const newBlockText = newBlock.getText();
            const oldBlockText = oldBlock.getText();

            // 检查文本是否发生变化
            if (oldBlockText !== newBlockText) {
                console.log("检查到文本发生变化-old", oldBlockText);
                console.log("检查到文本发生变化-new", newBlockText);
                const currentBlockParagraphType = getEditorBlockParagraphTypeByContentBlock(newBlock);
                updateTopicAttributeByTopicId(currentBlockParagraphType, newBlock, newContentBlockMap, newContentState, true);
                // if (
                //     currentBlockParagraphType == 'custom_background_paragraph' ||
                //     currentBlockParagraphType == 'default_background_paragraph'
                // ) {
                //     //文本段落修改
                //     updateTopicAttributeByTopicIdDelay(currentBlockParagraphType, newBlock, newContentBlockMap, newContentState);
                // } else {
                //     console.log("currentBlockParagraphType--->else", currentBlockParagraphType)
                //     updateTopicAttributeByTopicIdDelay(currentBlockParagraphType, newBlock, newContentBlockMap, newContentState);
                //     // updateTopicAttributeByTopicIdDelay(currentBlockParagraphType, newBlock, newContentBlockMap, newContentState);
                // }
            } else if (newBlockText === oldBlockText) {
                console.log("未检测到文本变化，开始检测文本样式改变");
                const newBlockTextLength = newBlockText.length;
                for (let i = 0; i < newBlockTextLength; i++) {
                    const oldStyle = oldBlock.getInlineStyleAt(i);
                    const newStyle = newBlock.getInlineStyleAt(i);
                    if (!oldStyle.equals(newStyle)) {
                        console.log("段落样式改变了")
                        // console.log(`Style of character at index ${i} in block with key ${blockKey} has changed.`);
                        break;
                    }
                }
            }
            // 检查每个字符的样式是否发生变化
            // const oldCharList = oldBlock.getCharacterList();
            // const newCharList = newBlock.getCharacterList();
            // // console.log("oldCharList----->", oldCharList)
            // for (let i = 0; i < newCharList.size; i++) {
            //     const oldCharStyle = oldCharList.get(i).getStyle();
            //     const newCharStyle = newCharList.get(i).getStyle();
            //     // console.log("oldCharStyle--->", oldCharStyle)
            //     // if (!oldCharStyle.equals(newCharStyle)) {
            //     //     console.log(`Style of character at index ${i} in block with key ${blockKey} has changed.`);
            //     // }
            // }
        })
        oldContentBlockMap.forEach((block, key) => {
            if (!newContentBlockMap.has(key)) {
                console.log('被删除的块 key:', key);
                //根据被删除的key, 更新textTopic下的wordParagraphList;
                updateTopicWhenPagraphDeleteDelay(block, key);
            }
        })
        handleUpdateEditorState(newEditorState)
    };

    const updateTopicWhenPagraphDeleteDelay = (
        currentBlock: ContentBlock,
        blockKey: string
    ) => {
        if (updateTopicAttributeDelayTimer3.current) {
            clearTimeout(updateTopicAttributeDelayTimer3.current)
        }
        updateTopicAttributeDelayTimer3.current = setTimeout(() => {
            let _tempComDocInstance = tempComDocInstance.current;
            let _tempTopicList = _tempComDocInstance.topicList;
            const wordParagrah: WordParagraphBlock = currentBlock.getData().get('wordParagraph')
            console.log("wordParagrah--->", wordParagrah)
            const findTextTopic = _tempTopicList.find(topic => {
                return topic.id == wordParagrah.textTopicId;
            })
            const wordParagraphList = findTextTopic.wordParagraphList;
            for (let i = 0; i < wordParagraphList.length; i++) {
                if (wordParagraphList[i].blockId === blockKey) {
                    wordParagraphList.splice(i, 1);
                    break;
                }
            }
            findTextTopic.wordParagraphList = [...wordParagraphList];
            _tempComDocInstance.topicList = [..._tempTopicList];
            _tempComDocInstance = { ..._tempComDocInstance };
            tempComDocInstance.current = _tempComDocInstance;
            handleUpdateComDocInstance(_tempComDocInstance);
            refreshWordEditorState();
        }, 1000);
    }

    const findSimilarBlocksForBackgroundParagraph = (blockKey: string, blockMap: BlockMap): ContentBlock[] => {
        const prefix = blockKey.substring(0, blockKey.lastIndexOf("_") + 1);
        const similarBlocks = [];
        blockMap.forEach((block) => {
            if (block.getKey().startsWith(prefix)) {
                similarBlocks.push(block);
            }
        });
        return similarBlocks;
    }

    // /**
    //  * word模块更新信息-延迟触发
    //  * @param paragraphType 
    //  * @param blockKey 
    //  * @param blockMap 
    //  * @param newBlock 
    //  * @param contentState 
    //  */
    // const updateTopicAttributeByTopicIdDelay = (
    //     paragraphType: WordParagraphType,
    //     newBlock: ContentBlock,
    //     blockMap: BlockMap,
    //     contentState: ContentState,
    // ) => {
    //     console.log("走updateTopicAttributeByTopicIdDelay")
    //     if (updateTopicAttributeDelayTimer1.current) {
    //         clearTimeout(updateTopicAttributeDelayTimer1.current)
    //     }
    //     updateTopicAttributeDelayTimer1.current = setTimeout(() => {
    //         updateTopicAttributeByTopicId(
    //             paragraphType,
    //             newBlock,
    //             blockMap,
    //             contentState,
    //             true
    //         )
    //     }, 1500);
    // }

    /**
     * word模块更新信息
     * @param paragraphType 
     * @param blockKey 
     * @param blockMap 
     * @param newBlock 
     * @param contentState 
     */
    const updateTopicAttributeByTopicId = (
        paragraphType: WordParagraphType,
        newBlock: ContentBlock,
        blockMap: BlockMap,
        contentState: ContentState,
        synchronizationContextState?: boolean
    ) => {
        if (updateTopicAttributeDelayTimer2.current) {
            clearTimeout(updateTopicAttributeDelayTimer2.current)
        }
        updateTopicAttributeDelayTimer2.current = setTimeout(() => {
            const newInlineStyleRanges = getInlineStyleRangesForBlock(newBlock);
            console.log("newInlineStyleRanges--->", newInlineStyleRanges)
            const newBlockKey = newBlock.getKey();
            const newBlockData = newBlock.getData();
            const newBlockText = newBlock.getText();
            console.log("newBlockText--->", newBlockText)
            const wordParagraphBlock: WordParagraphBlock = newBlockData.get('wordParagraph');
            console.log("当前更改的block的wordParagraphBlock---->", wordParagraphBlock)
            const _tempTopicList = tempTopicList.current;
            const _tempComDocInstance = comDocInstance;
            for (let i = 0; i < _tempTopicList.length; i++) {
                if (wordParagraphBlock.textTopicId === _tempTopicList[i].id) {
                    const currentTextTopic = _tempTopicList[i];
                    console.log("Editor编辑器改动时-找到了需要更新的topic----->", currentTextTopic)
                    const currentWordParagraphList = currentTextTopic.wordParagraphList;
                    const findWordParagraph = currentWordParagraphList.find(wordParagraph => {
                        return wordParagraph.blockId == newBlockKey;
                    })
                    if (findWordParagraph) {
                        console.log("找到了对应的wordParagraph---->", findWordParagraph)
                        //更新styleRange是非常有必要的
                        findWordParagraph.inlineStyleRanges = newInlineStyleRanges;
                        switch (paragraphType) {
                            case 'topic_title':
                                let newTopicNameList = newBlockText.split(_tempTopicList[i].serialNumber);
                                let newTopicName = "";
                                console.log("newTopicName---->", newTopicNameList, newTopicName)
                                if (newTopicNameList.length > 1) {
                                    newTopicName = newTopicNameList[1].trim();
                                }
                                _tempTopicList[i].topicName = newTopicName;
                                break;
                            case 'default_background_paragraph':
                            case 'custom_background_paragraph':
                                console.log("开始更新系统内置背景文本和自定义纯文本段落", findWordParagraph, newBlockText)
                                findWordParagraph.text = newBlockText;
                                break;
                            case 'device_background_paragraph':
                                console.log("要开始更新设备的描述文本段落了------>", newBlockText);
                                //获取这个段落文本block中的所有entity的最新信息、把这个block中所有的entity都更新一遍
                                const deviceParagraphSpecialTextEntities = getDeviceParagraphSpecialTextEntities(newBlock, contentState);
                                console.log("更新前findWordParagraph.entityRanges-->", [...findWordParagraph.entityRanges])
                                let _deviceEntityRanges = findWordParagraph.entityRanges;
                                for (let e = 0; e < _deviceEntityRanges.length; e++) {
                                    //topic中记录的entity信息
                                    let currentDeviceEntityRange = _deviceEntityRanges[e];
                                    const findNewEnitityInfo = deviceParagraphSpecialTextEntities.find(deviceParagraphSpecialTextEntitie => {
                                        const _deviceEntityRange: DeviceEntityRange = deviceParagraphSpecialTextEntitie.data;
                                        return _deviceEntityRange.textTopicId == currentDeviceEntityRange.textTopicId &&
                                            getDeviceEntityTag(_deviceEntityRange) == getDeviceEntityTag(currentDeviceEntityRange) &&
                                            _deviceEntityRange.key == currentDeviceEntityRange.key;
                                    })
                                    console.log("findNewEnitityInfo--->", findNewEnitityInfo)
                                    if (findNewEnitityInfo) {
                                        currentDeviceEntityRange.textOffset = findNewEnitityInfo.offset;
                                        currentDeviceEntityRange.start = findNewEnitityInfo.offset;
                                        currentDeviceEntityRange.end = findNewEnitityInfo.end;
                                        currentDeviceEntityRange.textLength = findNewEnitityInfo.length;
                                    }
                                }
                                console.log("更新后_deviceEntityRanges------>", _deviceEntityRanges, newBlockText)
                                findWordParagraph.text = newBlockText;
                                findWordParagraph.entityRanges = deepCopy(_deviceEntityRanges);
                                break;
                            default:
                                break;
                        }
                    }
                    break;
                }
            }
            _tempComDocInstance.topicList = deepCopy(_tempTopicList);
            if (synchronizationContextState) {
                handleUpdateComDocInstance(deepCopy(_tempComDocInstance));
            }
        }, 200);
    }



    const onEditorFocus = () => {
        isEditorFocus.current = true;
    }

    const onEditorBlur = () => {
        isEditorFocus.current = false;
        // console.log("onEditorBlur---->")
        // handleCloseWordEditorContextMenu();
    }

    const getBlockStyle = (block: any) => {
        switch (block.getType()) {
            case 'unstyled':
                return 'normal_paragraphblock';
            case 'blockquote':
                return 'RichEditor-blockquote';
                break;
            case 'title_paragraph_1':
                return 'title_paragraph_1_style';
                break;
            case 'title_paragraph_2':
                return 'title_paragraph_2_style';
                break;
            case 'title_paragraph_3':
                return 'title_paragraph_3_style';
                break;
            case 'title_paragraph_4':
                return 'title_paragraph_4_style';
                break;
            case 'title_paragraph_5':
                return 'title_paragraph_5_style';
                break;
            case 'title_paragraph_6':
                return 'title_paragraph_6_style';
            case 'table_name_paragraph':
                return 'table_name_paragraph_style';
            case 'normal_paragraph':
                return 'normal_paragraph_style';
                break;

            default:
                return null;
                break;
        }
    }

    const customBlockRenderer = (contentBlock, additionalProps) => {
        const type = contentBlock.getType();
        if (type === 'atomic') {
            const contentState = editorState.getCurrentContent();
            const entityKey = contentBlock.getEntityAt(0);
            const entity = contentState.getEntity(entityKey);
            const entityType = entity.getType();

            if (entityType === 'SPECIAL_TEXT') {
                return {
                    component: SpecialTextWithInput,
                    editable: false,
                    props: {
                        ...additionalProps,
                        entityKey: entityKey,
                    },
                };
            }
        }
        return null;
    };

    const findEntityRange = (contentState, entityKey) => {
        let entityRange = null;
        contentState.getBlockMap().forEach((block) => {
            block.findEntityRanges(
                (character) => character.getEntity() === entityKey,
                (start, end) => {
                    entityRange = {
                        startKey: block.getKey(),
                        startOffset: start,
                        endKey: block.getKey(),
                        endOffset: end,
                    };
                }
            );
        });
        return entityRange;
    }

    const deleteEntityAtSelection = (editorState, entityKey = null) => {
        const contentState = editorState.getCurrentContent();
        const selectionState = editorState.getSelection();

        // 寻找实体的开始和结束位置
        const startKey = selectionState.getStartKey();
        const startOffset = selectionState.getStartOffset();
        const block = contentState.getBlockForKey(startKey);
        entityKey = entityKey || block.getEntityAt(startOffset - 1);

        const entityRange = findEntityRange(contentState, entityKey);

        if (!entityRange) {
            return editorState;
        }

        // 创建一个选择整个实体的新选择范围
        const newSelection = selectionState.merge({
            anchorKey: entityRange.startKey,
            anchorOffset: entityRange.startOffset,
            focusKey: entityRange.endKey,
            focusOffset: entityRange.endOffset,
        });

        // 删除选择范围内的实体
        const newContentState = Modifier.removeRange(contentState, newSelection, 'backward');
        const newEditorState = EditorState.push(editorState, newContentState, 'remove-range');

        // 更新光标位置
        const updatedSelection = newEditorState.getSelection().merge({
            anchorOffset: entityRange.startOffset,
            focusOffset: entityRange.startOffset,
        });
        return EditorState.forceSelection(newEditorState, updatedSelection);
    }

    const insertTextWithoutAffectingEntities = (contentState, selectionState, text) => {
        const startKey = selectionState.getStartKey();
        const startOffset = selectionState.getStartOffset();
        const block = contentState.getBlockForKey(startKey);
        const currentEntityKey = block.getEntityAt(startOffset - 1);

        const newContentState = Modifier.insertText(contentState, selectionState, text, null, currentEntityKey);
        return newContentState;
    };

    const handleBeforeInput = (chars, editorState: EditorState) => {
        // if (isComposing.current) {
        //     event.stopPropagation();
        //   }
        // const selection = editorState.getSelection();
        // const currentContent = editorState.getCurrentContent();
        // const currentBlock = currentContent.getBlockForKey(selection.getStartKey());
        // const currentBlockText = currentBlock.getText();
        // const paragraphTitleMatch = checkIsParagraphTitle(currentBlockText);
        // const chapterTitleRegex = /^第\s*\d+\s*章/;
        // const chapterTitleMatch = currentBlockText.match(chapterTitleRegex);
        // if (
        //     paragraphTitleMatch &&
        //     (
        //         selection.getStartOffset() <= paragraphTitleMatch[0].length ||
        //         chars === "." ||
        //         (chapterTitleMatch && selection.getStartOffset() < chapterTitleMatch[0].length)
        //     )
        // ) {
        //     return "handled";
        // }
        const contentState = editorState.getCurrentContent();
        const selectionState = editorState.getSelection();
        const newContentState = insertTextWithoutAffectingEntities(contentState, selectionState, chars);
        onEditorStateChange(EditorState.push(editorState, newContentState, 'insert-characters'));
        return 'handled';
    };

    const handleKeyCommand = (command: string, editorState: EditorState): 'handled' | 'not-handled' => {
        console.log("command--->", command)
        let deleteCommandKeys = ['backspace', 'backspace-word', 'delete'];
        if (deleteCommandKeys.includes(command)) {
            const selection = editorState.getSelection();
            const currentContent = editorState.getCurrentContent();
            const currentBlock = currentContent.getBlockForKey(selection.getStartKey());
            const currentBlockText = currentBlock.getText();
            // console.log("当前操作的段落文本是---->", currentBlockText)
            if (selection.isCollapsed()) {
                const contentState = editorState.getCurrentContent();
                const currentBlock = contentState.getBlockForKey(selection.getStartKey());
                const offset = selection.getStartOffset();
                // 检查当前光标位置是否在实体后面
                const prevCharEntityKey = currentBlock.getEntityAt(offset - 1);
                if (prevCharEntityKey) {
                    // 删除整个实体
                    toastShort("error", "若需要删除段落中的设施/设备输入框，请在大纲库中取消勾选对应节点")
                    // const newEditorState = deleteEntityAtSelection(editorState, prevCharEntityKey);
                    // handleUpdateEditorState(newEditorState);
                    return 'handled';
                } else {
                    const paragraphTitleMatch = checkIsParagraphTitle(currentBlockText);
                    if (paragraphTitleMatch && selection.getStartOffset() <= paragraphTitleMatch[0].length) {
                        // 阻止用户删除标题内的文本
                        return "handled";
                    } else {
                        if (selection.getStartOffset() === 0) {
                            toastShort('error', '请勿尝试主动合并报告段落')
                            return 'handled';
                        }
                    }
                }
            }
            const newState = RichUtils.handleKeyCommand(editorState, command);
            if (newState) {
                handleUpdateEditorState(newState);
                return 'handled';
            }
        }

        return 'not-handled';
    };

    const handlePastedText = (text, html, editorState) => {
        const contentState = editorState.getCurrentContent();
        const selectionState = editorState.getSelection();
        const newContentState = Modifier.insertText(contentState, selectionState, text);
        onEditorStateChange(EditorState.push(editorState, newContentState, 'insert-fragment'));
        return 'handled';
    };

    const onCompositionStart = () => {
        isComposing.current = true;
    };

    const onCompositionupdate = (event) => {
        console.log("正在输入中....")
    }

    const onCompositionEnd = () => {
        isComposing.current = false;
    };


    useEffect(() => {
        const el = wordEditorRef.current?.editor;
        if (el) {
            el.addEventListener('compositionstart', onCompositionStart);
            el.addEventListener('compositionend', onCompositionEnd);
            el.addEventListener('compositionupdate', onCompositionupdate)
        }
        return () => {
            if (el) {
                el.removeEventListener('compositionstart', onCompositionStart);
                el.removeEventListener('compositionend', onCompositionEnd);
            }
        };
    }, [wordEditorRef]);

    const handleSetCurrentEntityOffsetWidth = (newDeviceEntityCache: DeviceEntityRange) => {
        // console.log("handleSetCurrentEntityOffsetWidth---->")
        let _deviceEntityRangeCacheList = deviceEntityRangeCacheList.current;
        const findDeviceEntityRangeCache = _deviceEntityRangeCacheList.find(entityRangeCache => {
            return entityRangeCache.deviceAttributeType + entityRangeCache.deviceTopicId == newDeviceEntityCache.deviceAttributeType + newDeviceEntityCache.deviceTopicId;
        })
        if (findDeviceEntityRangeCache) {
            findDeviceEntityRangeCache.offsetWidth = newDeviceEntityCache.offsetWidth;
        } else {
            _deviceEntityRangeCacheList.push(newDeviceEntityCache);
        }
        // console.log("_deviceEntityRangeCacheList----->", _deviceEntityRangeCacheList)
    }

    const handleGetCurrentEntityOffsetWidth = (deviceEntityRange: DeviceEntityRange): number => {
        let entityOffsetWidth = 0;
        let _deviceEntityRangeCacheList = deviceEntityRangeCacheList.current;
        const findDeviceEntityRangeCache = _deviceEntityRangeCacheList.find(entityRangeCache => {
            return entityRangeCache.deviceAttributeType + entityRangeCache.deviceTopicId == deviceEntityRange.deviceAttributeType + deviceEntityRange.deviceTopicId;
        })
        if (findDeviceEntityRangeCache) {
            entityOffsetWidth = findDeviceEntityRangeCache.offsetWidth;
        }
        return entityOffsetWidth;
    }


    const onClickEditorContent = () => {
        console.log("编辑器聚焦-------->")
        // if (!isEditorFocus.current) {
        //     const newEditorState = moveSelectionToEnd(editorState);
        //     handleUpdateEditorState(newEditorState)
        // }
        if (isWordEditorContextMenuOpened) {
            // console.log("onClickEditorContent----->")
            handleCloseWordEditorContextMenu();
        }
        // 通过 EditorState 获取当前的 ContentState
        let contentState = editorState.getCurrentContent();
        // 通过 EditorState 获取当前的 SelectionState
        let selectionState = editorState.getSelection();
        // 通过 SelectionState 获取当前的 block key
        let blockKey = selectionState.getStartKey();
        const currentParagraphBlock: ContentBlock = contentState.getBlockForKey(blockKey);
        const wordParagraphBlock = currentParagraphBlock.getData().get('wordParagraph');
        const currentBlockText = currentParagraphBlock.getText();
        console.log("当前段落的文本是----->", currentBlockText)
        console.log("当前聚焦的段落是----->", wordParagraphBlock, currentParagraphBlock.getType(), blockKey);
        currentFocusedDocItemKey.current = blockKey;
        delaySetCurrentFocusParagraphBlockTimer.current = setTimeout(() => {
            _setCurrentFocusedDocItem(currentParagraphBlock)
            //处理高亮光标指示器
            let wordEditorFocusTrackLineHeight = 0;
            let wordEditorFocusTrackLineOffsetTop = 0;
            const blockEl = document.querySelector(`div[data-offset-key="${blockKey}-0-0"]`);
            //@ts-ignore 
            const blockOffsetTop = blockEl.offsetTop;
            if (wordEditorFocusTrackLineOffsetTop == 0) {
                wordEditorFocusTrackLineOffsetTop = blockOffsetTop;
            }
            wordEditorFocusTrackLineHeight += blockEl.clientHeight;
            console.log("wordEditorFocusTrackLineHeight--->", wordEditorFocusTrackLineHeight, wordEditorFocusTrackLineOffsetTop)
            wordEditorHighLightTrackLineRef.current.style.height = wordEditorFocusTrackLineHeight + 'px';
            wordEditorHighLightTrackLineRef.current.style.top = wordEditorFocusTrackLineOffsetTop + 'px';
        }, 100);
    };

    const onEdotorContentContextMenu = (e) => {
        // console.log("onContextMenu--->", e)
        const containerRect = containerRef.current.getBoundingClientRect();
        // console.log("containerRect--->", containerRect)
        // 聚焦编辑器
        if (wordEditorRef.current && !isEditorFocus.current) {
            wordEditorRef.current.focus();
        }
        const selection = editorState.getSelection();
        const nativeSelection = window.getSelection();
        const anchorNode = nativeSelection.anchorNode;

        // 获取节点的偏移量
        //@ts-ignore
        const anchorOffset = anchorNode ? anchorNode.parentNode.dataset.offset : 0;
        const focusOffset = nativeSelection.focusOffset;

        const newSelectionState = new SelectionState({
            anchorKey: selection.getAnchorKey(),
            anchorOffset,
            focusKey: selection.getFocusKey(),
            focusOffset,
            isBackward: false,
        });
        onEditorStateChange(EditorState.forceSelection(editorState, newSelectionState));
        wordEditorContextMenuRef.current.showContextMenu(e, containerRect);
        isWordEditorContextMenuOpened.current = true;
    }

    const handleReturn = (): DraftHandleValue => {
        const contentState = editorState.getCurrentContent();
        const selectionState = editorState.getSelection();
        const anchorKey = selectionState.getAnchorKey();
        const _anchorKey = currentFocusedDocItemKey.current ? currentFocusedDocItemKey.current : anchorKey;
        const currentBlock = contentState.getBlockForKey(_anchorKey);
        if (!currentBlock) {
            toastShort('error', '未找到聚焦段落')
            return 'handled';
        }
        const blockLength = currentBlock.getLength();
        const cursorPosition = selectionState.getStartOffset();
        let _tempComDocInstance = tempComDocInstance.current;
        let _tempTopicList = _tempComDocInstance.topicList;
        console.log("cursorPosition--->", cursorPosition, blockLength)
        if (cursorPosition === blockLength) {
            // console.log("段落文本是----->", currentBlock.getText())
            // 光标在段落的最末尾
            const wordParagrah: WordParagraphBlock = currentBlock.getData().get('wordParagraph');
            // console.log("wordParagrah--->", wordParagrah)
            const findTextTopic = _tempTopicList.find(topic => {
                return topic.id == wordParagrah.textTopicId;
            })
            // console.log("findTextTopic---->", findTextTopic)
            const wordParagraphList = findTextTopic.wordParagraphList;
            let findIndex = -1;
            for (let i = 0; i < wordParagraphList.length; i++) {
                if (wordParagraphList[i].blockId === _anchorKey) {
                    findIndex = i;
                    break;
                }
            }
            const newBlockId = generateBlockId();
            console.log("新的newBlockId---->", newBlockId)
            const newWordParagraph: WordParagraphBlock = {
                blockId: newBlockId,
                inlineStyleRanges: [],
                paragraphStyle: 'normal_paragraph',
                paragraphType: 'custom_background_paragraph',
                text: "",
                textTopicId: findTextTopic.id,
                type: 'text'
            }
            //更新currentFocusedDocItemKey
            currentFocusedDocItemKey.current = newBlockId;
            console.log("findIndex---->", findIndex);
            const newWordParagraphList = insertArrayAtPosition(wordParagraphList, [newWordParagraph], findIndex + 1);
            console.log("newWordParagraphList----->", newWordParagraphList);
            findTextTopic.wordParagraphList = [...newWordParagraphList];
            _tempComDocInstance.topicList = [..._tempTopicList];
            _tempComDocInstance = { ..._tempComDocInstance };
            tempComDocInstance.current = _tempComDocInstance;
            handleUpdateComDocInstance(_tempComDocInstance);
            refreshWordEditorState(newBlockId);
        } else {
            // if()
            console.log("光标不在段落的最末尾")
            toastShort('warning', '光标在段落的最末尾才允许分段')
        }
        return 'handled';
    }

    const customBlockRendererFn = (contentBlock: ContentBlock) => {
        const type = contentBlock.getType();
        // console.log("customBlockRendererFn---->Text", contentBlock.getText());
        // console.log("customBlockRendererFn---->Type", contentBlock.getType());
        switch (type) {
            case 'LaTex':
                return {
                    component: LaTexBlock,
                    editable: false,
                };
                break;
            case 'Table':
                return {
                    component: WordEditorTable,
                    editable: false,
                };
                break;
            case 'PageBreak':
                return {
                    component: PageBreakComponent,
                    editable: false,
                    props: {},
                };
                break;
            default:
                break;
        }
    }

    const onEdotorContentScroll = () => {
        handleCloseWordEditorContextMenu();
    };

    const handleCloseWordEditorContextMenu = () => {
        if (isWordEditorContextMenuOpened.current) {
            wordEditorContextMenuRef.current.hideContextMenu();
        }
    }

    const onWordEditorContextMenuClose = () => {
        isWordEditorContextMenuOpened.current = false;
    }

    return (
        <div
            ref={containerRef}
            className='word-edit-area-container content-border content-border-radius'
        >
            <div
                ref={scrollContentRef}
                className={adapContainerClassName()}
                onClick={onClickEditorContent}
                onScroll={onEdotorContentScroll}
            // onContextMenu={onEdotorContentContextMenu}
            >
                <div
                    ref={wordEditorFocusTrackLineRef}
                    className="word-editor-focus-track-line"
                ></div>
                <div
                    ref={wordEditorHighLightTrackLineRef}
                    className="word-editor-high-light-track-line"
                ></div>
                <EditorContext.Provider
                    value={{
                        onEntityChange: handleEntityChange,
                        setCurrentEntityOffsetWidth: handleSetCurrentEntityOffsetWidth,
                        getCurrentEntityOffsetWidth: handleGetCurrentEntityOffsetWidth
                    }}
                >
                    <Editor
                        ref={wordEditorRef}
                        editorState={editorState}
                        textAlignment={'left'}
                        textDirectionality={'LTR'}
                        placeholder={'报告文本为空...'}
                        stripPastedStyles={true}
                        onFocus={onEditorFocus}
                        onBlur={onEditorBlur}
                        //@ts-ignore
                        blockStyleFn={getBlockStyle}
                        customStyleMap={wordEditorStyleMap}
                        preserveSelectionOnBlur={true}
                        onChange={onEditorStateChange}
                        // handleBeforeInput={handleBeforeInput}
                        handleKeyCommand={handleKeyCommand}
                        handleReturn={handleReturn}
                        //@ts-ignore
                        handlePastedText={handlePastedText}
                        blockRendererFn={customBlockRendererFn}
                    />
                </EditorContext.Provider>

            </div>
            <WordEditorContextMenu
                ref={wordEditorContextMenuRef}
                onWordEditorContextMenuClose={onWordEditorContextMenuClose}
            />
        </div>
    )
}

export default forwardRef(WordEditorV2);
